package com.iussoft.receiveData.schedul;

import com.google.gson.JsonElement;
import com.google.gson.JsonObject;
import com.google.gson.JsonParser;
import com.iussoft.es.config.EsClientFactory;
import com.iussoft.es.entity.EsClientVo;
import com.iussoft.tools.LoggerUtil;
import com.netflix.appinfo.ApplicationInfoManager;
import com.netflix.appinfo.EurekaInstanceConfig;
import com.netflix.appinfo.InstanceInfo;
import com.netflix.discovery.DiscoveryManager;
import com.netflix.discovery.EurekaClientConfig;
import io.searchbox.client.JestResult;

import java.io.IOException;

/**
 * @description: ES健康检查实现
 * @author: Hou Dayu
 * @date: Created in 2020/3/1
 */
public class EsHealthCheckRunnable implements Runnable {

    private transient boolean EsHealth_DOWNLOAD_MARK = true;
    private transient boolean ES_DOWNLOAD_MARK = true;
    private final JsonParser jsonParser = new JsonParser();

    @Override
    public void run() {
        if(!EsHealth_DOWNLOAD_MARK){
            return ;
        }
        try{
            EsHealth_DOWNLOAD_MARK=false;
            if(EsClientFactory.getEsClientList("").size()>0) {
                EsClientFactory.getEsClientList("").removeIf(vo -> delJestClient(jsonParser, vo,false)==1);
            }
            EsClientFactory.getEsClientList("def").removeIf(vo-> delJestClient(jsonParser,vo,true)==0);
            if(ES_DOWNLOAD_MARK) {
                if (EsClientFactory.isDown()) {
                    ES_DOWNLOAD_MARK = false;
                    DiscoveryManager.getInstance().shutdownComponent();//下线
                    LoggerUtil.error("由于ES集群连接已全部断开，导致此服务被迫下线，请急时处理");
                }
            }
            if(!ES_DOWNLOAD_MARK){
                if (!EsClientFactory.isDown()) {//
                    EurekaClientConfig ecc = DiscoveryManager.getInstance().getEurekaClientConfig();
                    EurekaInstanceConfig eic = DiscoveryManager.getInstance().getEurekaInstanceConfig();
                    ApplicationInfoManager.getInstance().setInstanceStatus(InstanceInfo.InstanceStatus.UP);
                    DiscoveryManager.getInstance().initComponent(eic,ecc);
                    LoggerUtil.info("服务已恢复，重新上线成功");
                    ES_DOWNLOAD_MARK = true;
                }
            }
        }catch(Exception e){
            LoggerUtil.warn("check ES fail",e);
        }finally {
            EsHealth_DOWNLOAD_MARK=true;
        }
    }

    private int delJestClient(JsonParser jsonParser, EsClientVo vo, boolean mark){
        int count = 1;
        try {
            JestResult aliases = vo.getJestClient().execute((new io.searchbox.indices.Stats.Builder()).build());
            JsonElement root = jsonParser.parse(aliases.getJsonString());
            JsonObject shards = root.getAsJsonObject().get("_shards").getAsJsonObject();
            int failedShards = shards.get("failed").getAsInt();
            if (failedShards != 0) {
                LoggerUtil.warn("===ES调线了===");
                count = 0;
            }
        } catch (IOException e) {
            count = 0;
        }
        if(mark && count ==0){
            EsClientFactory.setCancelMap(vo);
        }else if(!mark && count ==1){
            EsClientFactory.delCancelMap(vo);
        }
        return count;
    }
}
